package com.geekhalo.demo.enums.code.fix;

import com.fasterxml.jackson.core.JsonParser;
import com.fasterxml.jackson.databind.DeserializationContext;
import com.fasterxml.jackson.databind.JsonDeserializer;
import com.geekhalo.lego.common.enums.CodeBasedEnum;
import org.apache.commons.lang3.StringUtils;
import org.springframework.boot.autoconfigure.jackson.Jackson2ObjectMapperBuilderCustomizer;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

import java.io.IOException;

@Configuration
public class CodeBasedEnumJacksonCustomizer {

//    @Bean
    public Jackson2ObjectMapperBuilderCustomizer commonEnumBuilderCustomizer(){
        return builder ->{
            // 注册自定义枚举反序列化器
            builder.deserializerByType(CodeBasedOrderStatus.class, new CommonEnumJsonDeserializer(CodeBasedOrderStatus.class));
        };
    }

    /**
     * 自定义枚举反序列化器
     */
    static class CommonEnumJsonDeserializer extends JsonDeserializer {
        private final Class codeBasedEnumCls;

        CommonEnumJsonDeserializer(Class codeBasedEnumCls) {
            this.codeBasedEnumCls = codeBasedEnumCls;
        }

        @Override
        public Object deserialize(JsonParser jsonParser, DeserializationContext deserializationContext) throws IOException {
            String value = jsonParser.readValueAs(String.class);
            if (StringUtils.isEmpty(value)) {
                return null;
            }
            // 遍历枚举所有 Value
            for (Object enumValue : codeBasedEnumCls.getEnumConstants()){
                // 判断枚举的 code
                String code = String.valueOf(((CodeBasedEnum) enumValue).getCode());
                if(value.equals(code)) {
                    return enumValue;
                }
                // 判断枚举 Name
                String name = ((Enum) enumValue).name();
                if (value.equals(name)){
                    return enumValue;
                }
            }
            return null;
        }
    }
}
